package workers;

import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.WindowEvent;
import java.awt.event.WindowListener;
import java.util.concurrent.BlockingQueue;
import java.util.logging.Level;
import java.util.logging.Logger;

import javax.swing.JOptionPane;

import com.ibm.mq.MQQueueManager;

import model.Software;
import workerUIs.StepFrame;
import workerUIs.TestFrame;
import workflow.step.IntegrationStep;

public class IntegrationStepWorker extends AbstractStepSwingWorker {

	private final String uiQueueName;

	public IntegrationStepWorker(StepFrame frame, String implQueueName, String uiQueueName,
			String outputQueueName) {
		super(frame, implQueueName, outputQueueName);
		this.uiQueueName = uiQueueName;
	}

	@Override
	protected void doStep(Software software) {
		new IntegrationStep().doStep(this.software);		
	}
	
	@Override
	protected Software doInBackground() throws Exception {
		try {
			final MQQueueManager qm = new MQQueueManager(IMQConstants.MQM_NAME);
			Software implSoftware = getMessage(qm, inputQueueName);
			Software uiSoftware = getMessage(qm, uiQueueName);
			this.software = mergeSoftware(implSoftware, uiSoftware);
			if (this.software != null) {
				doStep(this.software);
				putMessage(qm, outputQueueName, this.software);			
			}
			qm.disconnect();
			return this.software;
		} catch (Exception e) {
			logger.log(Level.SEVERE, "Exception when executing step: " + getClass().getName() + ": " + e.getMessage());
		}
		return null;
	}
	
	/**
	 * Pretty dummy merge of the software object come from the impl and ui.
	 * @param implSoftware
	 * @param uiSoftware
	 * @return
	 */
	private Software mergeSoftware(Software implSoftware, Software uiSoftware) {
		if (!implSoftware.getName().equals(uiSoftware.getName())) return null;
		Software software = new Software(implSoftware.getName());
		software.getComponents().addAll(implSoftware.getComponents());
		software.getComponents().addAll(uiSoftware.getComponents());
		software.setSystemDesignPlan(implSoftware.getSystemDesignPlan());
		return software;
	}

	public static void main(String[] args) {
		Logger logger = Logger.getLogger(ArchitectureStepWorker.class.getCanonicalName());
		try {			
			final StepFrame integrationFrame = new StepFrame("Step4: Integration", 1200, 200);
			integrationFrame.getNextButton().addActionListener(new ActionListener() {
				@Override
				public void actionPerformed(ActionEvent e) {
					new IntegrationStepWorker(integrationFrame, IMQConstants.IMPL_OUTPUT_INTEGRATION_INPUT, IMQConstants.UI_OUTPUT_INTEGRATION_INPUT, IMQConstants.INTEGRATION_OUTPUT_TEST_INPUT).execute();				
				}
			});
			new QueueDepthObserver().observeQueueDepth(integrationFrame, IMQConstants.IMPL_OUTPUT_INTEGRATION_INPUT, IMQConstants.UI_OUTPUT_INTEGRATION_INPUT);

		}
		catch (Exception e)
		{
			logger.log(Level.SEVERE, "Error during initialization: ", e);
		}
	}

}
